home *** CD-ROM | disk | FTP | other *** search
- /*
- * CParticle is an example CAfterDark subclass. It animates a particle
- * across the screen. Calculations are made so that the particle's
- * flight doesn't leave the screen. The animation isn't all that
- * great but it makes for a reasonable example.
- */
-
- #include "CParticle.h"
-
- /*
- * Initialize seeds the random number generator, gets the value for
- * gravity from the gravity slider, and then generates a set of initial
- * conditions.
- */
- OSErr CParticle::Init(RgnHandle blankRgn, GMParamBlockPtr params)
- {
- GetDateTime(&randSeed);
-
- G = params->controlValues[GRAVITY_CONTROL];
- this->InitialConditions(params);
-
- return noErr;
- }
-
-
- /*
- * Blank uses the superclasses blank method to blank the screen. It
- * then translates the origin for easier animation.
- */
- OSErr CParticle::Blank(RgnHandle blankRgn, GMParamBlockPtr params)
- {
- inherited::Blank(blankRgn, params);
- SetOrigin(0,-params->monitors->monitorList[0].bounds.bottom);
-
- return noErr;
- }
-
-
- /*
- * Draw performs animation by erasing the old particle at position
- * (X,Y), recalculating a new (X,Y) and then checks to see if the
- * particle has "fallen off" the bottom of the screen. If it has,
- * a new set of initial conditions is generated. If not, "time"
- * is incremented.
- */
- OSErr CParticle::DrawFrame(RgnHandle blankRgn, GMParamBlockPtr params)
- {
- Rect aRect;
-
- /*
- * Erase old particle
- */
- SetRect(&aRect, (int)X-4, (int)-Y-4, (int)X+4, (int)-Y+4);
- FillOval(&aRect, params->qdGlobalsCopy->qdBlack);
-
- /*
- * Calculate new particle position
- */
- Y = -G*T*T/2 + Vyo*T + Yo;
- X = Vxo*T + Xo;
-
- /*
- * If the particle is off the screen then generate a new set
- * of initial conditions otherwise draw the particle at the
- * new position.
- */
- if (Y < 0)
- this->InitialConditions(params);
- else {
- T += params->controlValues[DELTAT_CONTROL] / 100.0;
-
- SetRect(&aRect, (int)X-3, (int)-Y-3, (int)X+3, (int)-Y+3);
- FillOval(&aRect, params->qdGlobalsCopy->qdWhite);
- }
-
- return noErr;
- }
-
-
- /*
- * Move the origin to the normal location and then uses the superclasses
- * blank method to clear the screen.
- */
- OSErr CParticle::Close(RgnHandle blankRgn, GMParamBlockPtr params)
- {
- SetOrigin(0,0);
- inherited::Blank(blankRgn, params);
-
- return noErr;
- }
-
-
- /*
- * InitialConditions generates a set of random initial conditions
- * such that the particle will not fly beyond the top of the monitor
- * nor will it go beyond the sides of the monitor during its flight.
- */
- void CParticle::InitialConditions(GMParamBlockPtr params)
- {
- float maxX, maxY;
- int monitorX, monitorY, randomValue;
-
- monitorX = params->monitors->monitorList[0].bounds.right;
- monitorY = params->monitors->monitorList[0].bounds.bottom;
-
- T = X = Y = 0.0;
-
- do {
- randomValue = Random();
- randomValue = ABS(randomValue);
- Xo = randomValue % monitorX;
- Yo = 0.0;
-
- Vxo = Random() % params->controlValues[MAXVXO_CONTROL];
- randomValue = Random();
- randomValue = ABS(randomValue);
- Vyo = randomValue % params->controlValues[MAXVYO_CONTROL];
-
- maxX = 2*Vyo*Vxo/G + Xo;
- maxY = Vyo*Vyo/2/G + Yo;
- } while (maxY > monitorY || maxX < 0 || maxX > monitorX);
- }